#!/bin/bash
#set -euo pipefail

# 配置颜色输出
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # 无颜色

# 工具函数：信息提示
info() {
    echo -e "${BLUE}=== $1 ===${NC}"
}

# 工具函数：成功提示
success() {
    echo -e "${GREEN}✅ $1${NC}"
}

# 工具函数：警告提示
warning() {
    echo -e "${YELLOW}⚠️ $1${NC}"
}

# 工具函数：错误提示并退出
error_exit() {
    echo -e "${RED}❌ 错误：$1${NC}"
    exit 1
}

# 欢迎信息
echo -e "\n${BLUE}=== 安全Git仓库提交与推送工具 ===${NC}"

### 1. 检查Git是否安装
info "检查Git环境"
if ! command -v git &> /dev/null; then
    error_exit "未检测到Git工具，请先安装Git再执行脚本"
fi
success "Git已安装"

### 2. 初始化Git仓库（仅当未初始化时）
info "仓库初始化检查"
if [ ! -d ".git" ]; then
    read -p "未检测到Git仓库，是否初始化？(y/n)：" init_confirm
    if [[ "$init_confirm" =~ ^[Yy]$ ]]; then
        echo "执行: git init"
        git init || error_exit "仓库初始化失败"
        success "Git仓库初始化完成"
    else
        echo "用户取消初始化，脚本退出"
        exit 0
    fi
else
    success "已检测到Git仓库，跳过初始化"
fi

### 3. 配置远程仓库
info "远程仓库配置"
read -p "是否需要配置/更新远程仓库？(y/n)：" remote_confirm
if [[ "$remote_confirm" =~ ^[Yy]$ ]]; then
    read -p "请输入远程仓库URL（例：https://github.com/your-name/your-repo.git）：" remote_url

    # 验证URL格式
    if ! [[ "$remote_url" =~ ^(https?://|git@) ]]; then
        error_exit "远程URL格式无效（需以https://或git@开头）"
    fi

    # 处理已有远程配置
    if git remote | grep -q "origin"; then
        current_remote=$(git remote get-url origin)
        echo "当前origin远程地址：$current_remote"
        read -p "是否覆盖现有origin？(y/n)：" overwrite_confirm
        
        if [[ "$overwrite_confirm" =~ ^[Yy]$ ]]; then
            echo "执行: git remote rm origin"
            git remote rm origin
            echo "执行: git remote add origin $remote_url"
            git remote add origin "$remote_url" || error_exit "添加远程仓库失败"
        else
            echo "保留现有远程配置，跳过更新"
        fi
    else
        echo "执行: git remote add origin $remote_url"
        git remote add origin "$remote_url" || error_exit "添加远程仓库失败"
    fi

    # 验证远程连接
    echo -n "验证远程仓库连通性..."
    if ! git ls-remote --exit-code origin &> /dev/null; then
        error_exit "\n远程仓库连接失败（可能URL错误、无访问权限或网络问题）"
    fi
    success "远程仓库连接验证成功"
fi

### 4. 检查工作区状态
info "工作区状态检查"
has_changes=false
if ! git diff --quiet --cached --exit-code; then
    has_changes=true
elif [ -n "$(git ls-files --others --exclude-standard)" ]; then
    has_changes=true
fi

if [ "$has_changes" = false ]; then
    warning "工作区无修改文件"
    read -p "是否继续执行推送操作？(y/n)：" push_without_changes
    if ! [[ "$push_without_changes" =~ ^[Yy]$ ]]; then
        echo "无修改且用户取消推送，脚本退出"
        exit 0
    fi
    skip_commit=true
else
    skip_commit=false
fi

### 5. 添加文件到暂存区
if [ "$skip_commit" = false ]; then
    info "文件暂存操作"
    git status --short
    
    read -p "是否添加所有修改文件到暂存区？(y/n)：" add_confirm
    if [[ "$add_confirm" =~ ^[Yy]$ ]]; then
        # 检查.gitignore文件
        if [ ! -f ".gitignore" ]; then
            warning "未检测到.gitignore文件，可能导致敏感文件被提交！"
            read -p "是否继续添加所有文件？(y/n)：" ignore_confirm
            if ! [[ "$ignore_confirm" =~ ^[Yy]$ ]]; then
                echo "请先创建.gitignore文件配置忽略规则，脚本退出"
                exit 0
            fi
        fi
        echo "执行: git add ."
        git add . || error_exit "添加文件失败"
    else
        read -p "请输入需要添加的文件/目录（空格分隔，直接回车取消）：" add_files
        if [ -n "$add_files" ]; then
            echo "执行: git add $add_files"
            git add $add_files || error_exit "添加指定文件失败"
        else
            echo "未添加任何文件，脚本退出"
            exit 0
        fi
    fi
    success "文件暂存完成"
fi

### 6. 输入提交信息
commit_message=""
if [ "$skip_commit" = false ]; then
    info "提交信息设置"
    echo "提交信息规范提示："
    echo "  <类型>[可选作用域]: <描述>"
    echo "  例：feat(login): 增加验证码登录功能"
    echo "  类型：feat(新功能)、fix(修复)、docs(文档)、style(格式)、refactor(重构)、test(测试)、chore(构建)"

    while true; do
        read -p "请输入提交信息：" commit_message
        if [ -n "$commit_message" ] && [ ${#commit_message} -ge 5 ]; then
            break
        fi
        warning "提交信息不能为空且长度需≥5个字符，请重新输入"
    done
fi

### 7. 提交更改
if [ "$skip_commit" = false ]; then
    info "提交变更确认"
    echo "即将提交的变更："
    git diff --cached --name-status
    
    read -p "确认提交以上变更？(y/n)：" commit_confirm
    if [[ "$commit_confirm" =~ ^[Yy]$ ]]; then
        echo "执行: git commit -m '$commit_message'"
        git commit -m "$commit_message" || error_exit "提交失败"
        success "本地提交完成"
    else
        echo "用户取消提交，脚本退出"
        exit 0
    fi
fi

### 8. 推送至远程仓库
info "远程推送操作"
# 获取当前分支
current_branch=$(git rev-parse --abbrev-ref HEAD 2>/dev/null || :)
if [ -z "${current_branch:-}" ]; then
    error_exit "无法获取当前分支名称，可能仓库未初始化或没有提交记录"
fi
echo "当前分支：$current_branch"

# 构建推送命令
push_cmd=""
if ! git ls-remote --exit-code --heads origin "${current_branch}" &> /dev/null; then
    warning "远程仓库不存在$current_branch分支，将执行首次推送（自动关联分支）"
    push_cmd="git push -u origin $current_branch"
else
    # 非首次推送：先拉取远程更新
    echo "执行: git fetch origin $current_branch (获取远程更新)"
    git fetch origin "$current_branch" || error_exit "获取远程更新失败"
    
    # 检查是否落后于远程
    if [ "$(git rev-list HEAD..origin/"$current_branch" --count)" -gt 0 ]; then
        warning "本地分支落后于远程分支，需要合并远程更改"
        
        echo "执行: git merge origin/$current_branch (合并远程更改)"
        if ! git merge origin/"$current_branch"; then
            error_exit "合并远程更改时发生冲突，请手动解决冲突后再运行脚本"
        fi
        
        # 再次检查
        git fetch origin "$current_branch"
        if [ "$(git rev-list HEAD..origin/"$current_branch" --count)" -gt 0 ]; then
            error_exit "合并后仍落后于远程分支，请再次合并远程更改"
        fi
    fi
    push_cmd="git push origin $current_branch"
fi

# 确认并执行推送
read -p "是否执行推送：$push_cmd？(y/n)：" push_confirm
if [[ "$push_confirm" =~ ^[Yy]$ ]]; then
    echo "执行: $push_cmd"
    if ! $push_cmd; then
        error_exit "推送失败！可能原因：远程有新提交、无权限或网络问题"
    fi
    success "远程推送完成"
else
    echo "用户取消推送，脚本退出"
    exit 0
fi

### 完成信息
info "操作总结"
if [ "$skip_commit" = false ]; then
    echo -e "分支: ${YELLOW}$current_branch${NC}"
    echo -e "提交信息: ${YELLOW}$commit_message${NC}"
    echo -e "远程仓库: ${YELLOW}$(git remote get-url origin)${NC}"
else
    echo -e "推送分支: ${YELLOW}$current_branch${NC}"
    echo -e "远程仓库: ${YELLOW}$(git remote get-url origin)${NC}"
fi
success "所有操作已成功完成！"

exit 0
